/* USER CODE BEGIN Header */
/**
 ******************************************************************************
 * File Name          : freertos.c
 * Description        : Code for freertos applications
 ******************************************************************************
 * @attention
 *
 * Copyright (c) 2025 STMicroelectronics.
 * All rights reserved.
 *
 * This software is licensed under terms that can be found in the LICENSE file
 * in the root directory of this software component.
 * If no LICENSE file comes with this software, it is provided AS-IS.
 *
 ******************************************************************************
 */
/* USER CODE END Header */

/* Includes ------------------------------------------------------------------*/
#include <stdio.h>
#include "FreeRTOS.h"
#include "task.h"
#include "main.h"
#include "cmsis_os.h"

/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "elog.h"
#include "usart.h"
#include "queue.h"
#include "ymodem.h"
#include "OTA.h"
/* USER CODE END Includes */

/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */

/* USER CODE END PTD */

/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */

/* USER CODE END PD */

/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */

/* USER CODE END PM */

/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN Variables */

/* USER CODE END Variables */
/* Definitions for defaultTask */
osThreadId_t         defaultTaskHandle;
const osThreadAttr_t defaultTask_attributes = {
    .name       = "defaultTask",
    .stack_size = 128 * 4,
    .priority   = (osPriority_t)osPriorityNormal,
};

/* Private function prototypes -----------------------------------------------*/
/* USER CODE BEGIN FunctionPrototypes */

/* USER CODE END FunctionPrototypes */

void StartDefaultTask( void *argument );

void MX_FREERTOS_Init( void ); /* (MISRA C 2004 rule 8.1) */

/**
 * @brief  FreeRTOS initialization
 * @param  None
 * @retval None
 */
void MX_FREERTOS_Init( void )
{
    /* USER CODE BEGIN Init */

    /* USER CODE END Init */

    /* USER CODE BEGIN RTOS_MUTEX */
    /* add mutexes, ... */
    /* USER CODE END RTOS_MUTEX */

    /* USER CODE BEGIN RTOS_SEMAPHORES */
    /* add semaphores, ... */
    /* USER CODE END RTOS_SEMAPHORES */

    /* USER CODE BEGIN RTOS_TIMERS */
    /* start timers, add new ones, ... */
    /* USER CODE END RTOS_TIMERS */

    /* USER CODE BEGIN RTOS_QUEUES */
    /* add queues, ... */
    Queue_OTA_cmd = xQueueCreate( 1, sizeof( uint16_t ) );
    /* USER CODE END RTOS_QUEUES */

    /* Create the thread(s) */
    /* creation of defaultTask */
    defaultTaskHandle = osThreadNew( StartDefaultTask, NULL, &defaultTask_attributes );

    /* USER CODE BEGIN RTOS_THREADS */
    /* add threads, ... */
    OTA_taskHandle = osThreadNew( ota_task, NULL, &OTA_task_attributes );
    /* USER CODE END RTOS_THREADS */

    /* USER CODE BEGIN RTOS_EVENTS */
    /* add events, ... */
    /* USER CODE END RTOS_EVENTS */
}

/* USER CODE BEGIN Header_StartDefaultTask */
/**
 * @brief  Function implementing the defaultTask thread.
 * @param  argument: Not used
 * @retval None
 */
/* USER CODE END Header_StartDefaultTask */
void StartDefaultTask( void *argument )
{
    /* USER CODE BEGIN StartDefaultTask */
    /* Infinite loop */
    log_i( "StartDefaultTask!\r\n" );

    for ( ;; )
    {
        HAL_GPIO_WritePin( LED_GPIO_Port, LED_Pin, GPIO_PIN_RESET );
        osDelay( 100 );
        HAL_GPIO_WritePin( LED_GPIO_Port, LED_Pin, GPIO_PIN_SET );
        osDelay( 500 );
    }
    /* USER CODE END StartDefaultTask */
}

/* Private application code --------------------------------------------------*/
/* USER CODE BEGIN Application */
extern DMA_HandleTypeDef hdma_usart1_rx;
void                     HAL_UARTEx_RxEventCallback( UART_HandleTypeDef *huart, uint16_t Size )
{
    UNUSED( huart );
    UNUSED( Size );
    uint16_t   rec_length               = 0;
    BaseType_t xHigherPriorityTaskWoken = pdFALSE;

    // 判断是串口1
    if ( huart->Instance == USART1 )
    {
        // 获取剩余当前传输值
        if ( 1 == __HAL_UART_GET_FLAG( huart, UART_FLAG_IDLE ) )
        {
            rec_length = Size;
            if ( pdFALSE != xQueueSendFromISR( Queue_OTA_cmd, &rec_length, 0 ) )
            {
                xHigherPriorityTaskWoken = pdTRUE;
            }
            HAL_UART_DMAStop( huart );
        }
        portYIELD_FROM_ISR( xHigherPriorityTaskWoken );
        // DMA 传输完成后的操作
    }
}
/* USER CODE END Application */
